package BaseUrls;
use strict;

use Data::Dumper;

use lib '/home/'.$ENV{HOSTUSER}.'/djpp/core/model';
use lib '/home/'.$ENV{HOSTUSER}.'/djpp/core/data';
use PreDefinedObjects;
use Controller;
use UrlInfo;
use YAML;
sub new
{
	my $class = shift;
	
	my $self = bless {
		controller404 	=> PreDefinedObjects->get404Controller,
		global_args		=> {},
	}, $class;
	
	$self->_init();
	
	return $self;
}

sub include
{
	my $self = shift;
	my $urls = shift;
	my $vars = shift;

	my $obj = eval "require $urls; return new $urls";
	$obj->{global_args} = $vars;
	
### FIXME ###
### Need refactor###	
	_add_global_vars($obj, $vars);
		
	return $obj;
}

sub _add_global_vars
{
	my ($obj, $vars) = @_;

	return unless $obj;
	while( my ($k, $v) = each (%$vars) ){
		$obj->{global_args}{$k} = $v unless $obj->{global_args}{$k}; 
	}
		
	for my $subobj (values( %{ $obj->{redirect_obj} } )){
		_add_global_vars($subobj, $vars);
	}
}

sub _init
{
	my $self = shift;	
	
	for my $info ( @{ $self->patterns } ){
		$self->add(
			url 	=> $info->[0],
			view 	=> $info->[1],
			args 	=> $info->[2] || undef,
			triggers => $info->[3] || undef,
		);
	}
}

sub add
{
	my $self = shift;
	my %args = @_;
	return unless $args{url};
	
	if (ref $args{view}){
		$self->_add_urls(%args);
	}
	else{
		$self->_add_view(%args);
	}
}

sub _add_urls
{
	my $self = shift;
	my %args = @_;	
	
	my $urlInfo = UrlInfo->create($args{url});
	
	push @{ $self->{redirect_url} }, $urlInfo->re;
	$self->{ redirect_obj }{ $urlInfo->re } = $args{view};
}

sub _add_view
{
	my $self = shift;
	my %args = @_;
	
	my $urlInfo = UrlInfo->create($args{url});
	
	return unless $args{view};
	my @arr = split /::/, $args{view};
	return if scalar (@arr) < 2;
	
	my $action = pop @arr;
	my $module = join("::", @arr);
		 
	my $ctl = new Controller(
		module 	=> $module,
		action 	=> $action,
		_args	=> $urlInfo->args,
		triggers => $args{triggers} || []
	);
	
	push @{ $self->{urls_arr} }, $urlInfo->re;
	
	$self->{urls_hash}{$urlInfo->re} = $ctl;
	$self->{urls_args}{$urlInfo->re} = $args{args} if $args{args};
}

sub handle
{
	my ($self, $url) = @_;
	
	my $controller = $self->{controller404};
	
	$url = add_slash($url);

	for my $re ( @{ $self->{redirect_url} } ){
		if ($url =~ /$re/){                   
			$url =~ s/($re)(.*)/$2/; 
			my $suburls = $self->{ redirect_obj }{ $re };  
			return $suburls->handle($url);
		}
	}
 	
	for my $re (@{ $self->{urls_arr} }){
		if($url =~ /$re/){ 
			$controller = $self->{urls_hash}{$re}; 
			for ( keys( %{$controller->_args} ) ){ 
				my $k = '$'.$controller->_args->{$_};
				$controller->args->{$_} = eval "$k";
			}
			
			for my $k (keys( %{ $self->{global_args} } ) ){
				$controller->args->{$k} = $self->{global_args}{$k};
			}

			for my $k (keys( %{ $self->{urls_args}{$re} } ) ){
				$controller->args->{$k} = $self->{urls_args}{$re}{$k};
			}
			last;
		}
	}
	
	return $controller;
}

sub add_slash
{
	my $url = shift;
	
	$url = "/".$url."/";
	$url =~ s/\/+/\//g;
	
	return $url;
}
1;
